/******************************************************************
 * Created by: Goh Chee Hong                                       
 * Date of Creation: 1/1/2009
 * Date of last modification: 31/1/2009
 * Status: Optimized and Finished
 *                                                                
 * Description: Sending a file
 ******************************************************************/
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Drawing;
using System.Data;
using System.Text;
using System.Windows.Forms;
using System.IO;
using System.Net;
using System.Net.Sockets;
using System.Threading;
using Pbdms.BusinessLogic;
using Pbdms.NetworkDealer;
using Pbdms.Common.DataObject;

namespace Pbdms.BusinessLogic.FileTransfer
{
    public partial class FileTransferSenderGui:FileTransferGui
    {
        

 
        
        private Thread thTransfer=null;

  
      


        public FileTransferSenderGui()
        {

        }
        public FileTransferSenderGui(string keyID,string friendName, System.IO.FileInfo fileInfo,Network.NetworkController networkController):base(){

            this.keyID = keyID;
            this.fileInfo = fileInfo;
            this.networkController = networkController;
            this.friendName = friendName;
            this.lblUser.Text = friendName;
            this.lblDoc.Text  = fileInfo.Name;
            this.lblStatus.Text = "Waiting for sending";
        }

        /// <summary>
        /// start method
        /// </summary>
        public override void start()
        {

            thTransfer = new Thread(new ThreadStart(send));
            thTransfer.IsBackground = true;
            thTransfer.Start();
            
        }
        /// <summary>
        /// send method
        /// </summary>
        private void send()
        {
            Buddy buddy = networkController.friendsControl.getAFriendByKeyID(keyID);
            FileStream file = null;
            authTcpClient = new AuthTcpClient(buddy.IpAdd, NetworkDealer.NetworkDealer.LISTEN_PORT, buddy.KeyID, networkController.keyControl, networkController.publicKeyControl, networkController.friendsControl);
            try
            {
                file = new FileStream(fileInfo.FullName, System.IO.FileMode.Open, System.IO.FileAccess.Read, FileShare.Read);

                authTcpClient.Connect();
                if (!authTcpClient.IsAuthenticated())
                {
                    displayStatus("Failed the handshaking");
                }

                NetworkMessage message = new NetworkMessage();
                message.TypeOfMessage = NetworkDealer.NetworkDealer.TRANSFER_FILE_REQUEST;
                message.MessageContent = fileInfo.Name + "," + fileInfo.Length.ToString();
                authTcpClient.sendMessage(message);
                displayStatus("Waiting for friend's reply");
                Thread.Sleep(1000);

                //get the reply back
                message = authTcpClient.receiveMessage();
                //wait for message

                if (message.TypeOfMessage == NetworkDealer.NetworkDealer.TRANSFER_FILE_REQUEST_GRANTED)
                {
                    displayStatus("Your friend has accepted the file transfer");
                    Thread.Sleep(1000);
                    int before = 0;
                    long rdby = 0;
                    long total = file.Length;
                    
                    byte[] buffed = null;
                    string currentDownload = Common.Global.GetFileSize(rdby);
                    string totalString = Common.Global.GetFileSize(total);
                    displayStatus( "Sending " + currentDownload + " of " + totalString);
                    while (rdby < total)
                    {
                        int length = 1024;
                        if (rdby + 1024 > total)
                        {
                            length = (int)(total - rdby);
                        }
                        buffed = new byte[length];
                        //Read from the File (len contains the number of bytes read)
                        int numBytesRead = 0;
                        while (length != numBytesRead)
                        {
                            // Read may return anything from 0 to numBytesToRead.
                            int n = file.Read(buffed, numBytesRead, length-numBytesRead);
                            numBytesRead += n;
                        }

                        //Write the Bytes on the Socket
                        authTcpClient.sendBytes(buffed);
                        //Increase the bytes Read counter
                        rdby = rdby + length;

                        int pc = (int)(((double)rdby / (double)total) * 100.00);
                        if (before != pc)
                        {
                            displayProgress(pc.ToString());
                            currentDownload = Common.Global.GetFileSize(rdby);
                            totalString = Common.Global.GetFileSize(total);
                            Thread.Sleep(100);
                        }
                        displayStatus("Sending " + currentDownload + " of " + totalString);
                        Thread.Sleep(100);
                        before = pc;
                       
                        
                    }
                    displayStatus("Finished sending");
                    Finished("");
                    authTcpClient.Close();
                }
                else
                {
                    ///receive a reject message
                    displayStatus("Your friend has rejected the file transfer");
                    Finished("");
                    Thread.Sleep(1000);
                }

            }
            catch
            {
                try
                {
                    displayStatus("The connection is disconnected");
                    Finished("");
                }
                catch
                {

                }
            }
            finally
            {
                finished = true;
                if (file != null)
                {
                    file.Close();
                }
            }


        }
   


               
    }
}
